package TCP;

import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;

/**
 * Day08_TestCallable 类用于演示使用 Callable 实现带返回值的线程任务。
 *
 * @author Cheng-02
 * @version V1.0
 * @since 2024/4/3 10:28
 */
public class Day08_TestCallable {
    public static void main(String[] args) {
        // 创建 CallableDemo 实例，用于执行卖票任务
        CalableDemo calableDemo = new CalableDemo();

        // 创建三个 FutureTask 实例，并绑定同一个 CallableDemo 实例，用于三个线程共享票务信息
        FutureTask<String> futureTask1 = new FutureTask<>(calableDemo);
        FutureTask<String> futureTask2 = new FutureTask<>(calableDemo);
        FutureTask<String> futureTask3 = new FutureTask<>(calableDemo);

        // 创建三个线程并启动，每个线程执行一个 FutureTask 任务
        Thread thread1 = new Thread(futureTask1, "窗口1");
        Thread thread2 = new Thread(futureTask2, "窗口2");
        Thread thread3 = new Thread(futureTask3, "窗口3");
        thread1.start();
        thread2.start();
        thread3.start();

        try {
            // 等待所有任务执行完成，并获取执行结果
            String info1 = futureTask1.get();
            String info2 = futureTask2.get();
            String info3 = futureTask3.get();

            // 打印结果
            System.out.println(info1);
            System.out.println(info2);
            System.out.println(info3);

        } catch (InterruptedException e) {
            // 处理线程中断异常
            throw new RuntimeException(e);
        } catch (ExecutionException e) {
            // 处理执行异常
            throw new RuntimeException(e);
        }

    }
}

/**
 * CallableDemo 类实现了 Callable 接口，用于定义一个可以返回结果的线程任务。
 */
class CalableDemo implements Callable<String> {
    int ticket = 100; // 定义初始票数

    /**
     * call 方法是 Callable 接口规定的方法，用于定义线程的具体执行逻辑。
     *
     * @return 返回一个字符串表示票已卖完。
     * @throws Exception 可能抛出的异常。
     */
    @Override
    public String call() throws Exception {
        while (true) {
            try {
                Thread.sleep(100); // 模拟卖票过程的延时
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            synchronized (this) {
                // 判断票数，若票数小于等于0，则结束卖票操作
                if (ticket <= 0) {
                    break;
                }
                // 输出卖票信息，并递减票数
                System.out.println(Thread.currentThread().getName() + "卖了" + ticket + "张票");
                ticket--;
            }
        }
        return "票卖完了"; // 返回结束信息
    }
}
